package com.bupt.ilink.service.impl;

import com.bupt.ilink.service.MinioService;
import io.minio.*;
import io.minio.errors.MinioException;
import io.minio.http.Method;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.util.Arrays;
import java.util.List;
import java.util.concurrent.TimeUnit;
@Service
public class MinioServiceImpl implements MinioService {
    private static final Logger logger = LoggerFactory.getLogger(MinioServiceImpl.class);

    private final MinioClient minioClient;

    @Value("${minio.url}")
    private String minioUrl;

    @Value("${minio.bucketName}")
    private String bucketName;

    // 支持的文件扩展名，可以根据需要添加其他格式
    private final List<String> fileExtensions = Arrays.asList("pdf", "docx", "xlsx", "md", "txt", "zip", "tar");

    //  支持的图片拓展名
//    private final List<String> imageExtensions = Arrays.asList("jpg", "jpeg", "png", "gif", "bmp", "tiff", "webp");
    private final List<String> imageExtensions = Arrays.asList("jpg", "jpeg", "png");

    //  支持的icon拓展名
    private final List<String> iconExtensions = Arrays.asList("svg", "jpeg", "png");

    private final List<String> StudyTreeExtensions = Arrays.asList("mp4", "jpg", "png");

    public MinioServiceImpl(@Value("${minio.url}") String url,
                            @Value("${minio.accessKey}") String accessKey,
                            @Value("${minio.secretKey}") String secretKey) {
        this.minioClient = MinioClient.builder()
                .endpoint(url)
                .credentials(accessKey, secretKey)
                .build();
    }

    @Override
    // 上传单个文件到MinIO的方法
    public String uploadSingleFile(String folder, String fileName, MultipartFile file) {
        try {
            // 构造目标文件路径
            String objectName = folder + "/" + fileName;

            // 上传文件到 MinIO
            minioClient.putObject(
                    PutObjectArgs.builder()
                            .bucket(bucketName)
                            .object(objectName)
                            .stream(file.getInputStream(), file.getSize(), -1)
                            .contentType(file.getContentType())
                            .build()
            );

            logger.info("文件 '{}' 上传到 '{}' 成功.", objectName, bucketName);

            // 返回文件的 URL
            return minioUrl + "/" + bucketName + "/" + objectName;
        } catch (Exception e) {
            logger.error("上传文件到MinIO时遇到错误：", e);
            return null;
        }
    }

    public void validateObjectExistence() {
        String objectName = "image/1816678340732522496.jpg"; // 硬编码测试对象名称
        boolean exists = doesObjectExist(objectName);
        logger.info("Object {} exists: {}", objectName, exists);
        if (exists) {
            String presignedUrl = getPresignedUrl(objectName);
            logger.info("Presigned URL for object {}: {}", objectName, presignedUrl);
        }
    }


    public String getPresignedUrl(String objectName) {
        try {
            // Generate a presigned URL valid for 1 hour
            String presignedUrl = minioClient.getPresignedObjectUrl(
                    GetPresignedObjectUrlArgs.builder()
                            .method(Method.GET)
                            .bucket(bucketName)
                            .object(objectName)
                            .expiry(1, TimeUnit.HOURS)
                            .build());
            logger.info("Generated presigned URL: {}", presignedUrl);
            return presignedUrl;
        } catch (Exception e) {
            logger.error("Error generating presigned URL for object: {}", objectName, e);
            return null;
        }
    }

    public boolean doesObjectExist(String objectName) {
        try {
            minioClient.statObject(
                    io.minio.StatObjectArgs.builder()
                            .bucket(bucketName)
                            .object(objectName)
                            .build());
            logger.info("Object exists: {}", objectName);
            return true;
        } catch (MinioException e) {
            logger.info("Object does not exist: {}", objectName, e);
            return false;
        } catch (Exception e) {
            logger.error("Unexpected error while checking object: {}", objectName, e);
            return false;
        }
    }

    @Override
    public String getImageUrlWithAnyFormat(String objectBaseName) {
        for (String format : imageExtensions) {
            String objectName = objectBaseName + "." + format;
            logger.info("Checking existence of object: {}", objectName);
            if (doesObjectExist(objectName)) {
                logger.info("Object found: {}", objectName);
                return getPresignedUrl(objectName);
            }
        }
        logger.warn("No object found for base name: {}", objectBaseName);
        return null; // 如果没有找到符合的格式，返回null
    }

    public String getFileUrlWithAnyFormat(String objectBaseName) {
        for (String format : fileExtensions) {
            String objectName = objectBaseName + "." + format;
            logger.info("Checking existence of object: {}", objectName);
            if (doesObjectExist(objectName)) {
                logger.info("Object found: {}", objectName);
                return getPresignedUrl(objectName);
            }
        }
        logger.warn("No object found for base name: {}", objectBaseName);
        return null; // 如果没有找到符合的格式，返回null
    }

    public String getIconUrlWithAnyFormat(String objectBaseName){
        for (String format : iconExtensions) {
            String objectName = objectBaseName + "." + format;
            logger.info("Checking existence of object: {}", objectName);
            if (doesObjectExist(objectName)) {
                logger.info("Object found: {}", objectName);
                return getPresignedUrl(objectName);
            }
        }
        logger.warn("No object found for base name: {}", objectBaseName);
        return null; // 如果没有找到符合的格式，返回null
    }

    public String getStudyTreeSourceUrlWithAnyFormat(String objectBaseName) {
        for (String format : StudyTreeExtensions) {
            String objectName = objectBaseName + "." + format;
            logger.info("Checking existence of object: {}", objectName);
            if (doesObjectExist(objectName)) {
                logger.info("Object found: {}", objectName);
                return getPresignedUrl(objectName);
            }
        }
        logger.warn("No object found for base name: {}", objectBaseName);
        return null; // 如果没有找到符合的格式，返回null
    }

}